﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Windows;
using System.Windows.Controls;
using System.Threading;
using Microsoft.Phone.Controls;
using Microsoft.Phone.Marketplace;
using Microsoft.Phone.Notification;
using Microsoft.Phone.Scheduler;
using Microsoft.Phone.Shell;
using Groovy_IM.Assets.Buddylist;
using Groovy_IM.Assets.Messages;
using System.Windows.Media;
using Groovy_IM.Assets;

namespace Groovy_IM
{
    public partial class MainPage : PhoneApplicationPage
    {
        private Dictionary<string, Group> collapsedGroups = new Dictionary<string, Group>();
        
        private Dictionary<string, MsgGroup> collapsedGroups2 = new Dictionary<string, MsgGroup>();

        //private Buddy selectedBuddy = null;

        public MainPage()
        {
            InitializeComponent();

            this.Loaded += new RoutedEventHandler(MainPage_Loaded);

            this.BackKeyPress += new EventHandler<System.ComponentModel.CancelEventArgs>(MainPage_BackKeyPress);

            LicenseInformation li = new LicenseInformation();

            if (li.IsTrial())
                showADs.Visibility = Visibility.Visible;
            else
                showADs.Visibility = Visibility.Collapsed;

            App.m_Actions.AddAccounts += new Actions.AddAccount2(m_Actions_AddAccounts);
        }

        void m_Actions_AddAccounts(int Account)
        {
            Account = Account - 1;

            App.m_Proto[Account] = new Protocols.Protocol();

            if (App.Accounts.Items[Account].AutoLogin == true)
            {
                App.setProgressIndication(this, true, true, "Connecting", 0);

                App.m_Proto[Account].SignOn(Account);
            }

            App.m_Proto[Account].BuddyChatUpdate += new Protocols.Protocol.BuddyChatUpdate2(BuddyChatUpdate);

            App.m_Proto[Account].BuddyGroup += new Protocols.Protocol.BuddyGroup2(BuddyGroup);

            App.m_Proto[Account].BuddyItem += new Protocols.Protocol.BuddyItem2(BuddyItem);

            App.m_Proto[Account].BuddyStatusUpdate += new Protocols.Protocol.BuddyStatusUpdate2(BuddyStatusUpdate);

            App.m_Proto[Account].IncomingChatInvite += new Protocols.Protocol.IncomingChatInvite2(IncomingChatInvite);

            App.m_Proto[Account].IncomingChatMessage += new Protocols.Protocol.IncomingChatMessage2(IncomingChatMessage);

            App.m_Proto[Account].IncomingICBM += new Protocols.Protocol.IncomingICBM2(IncomingICBM);

            App.m_Proto[Account].IncomingUserIcon += new Protocols.Protocol.IncomingUserIcon2(IncomingUserIcon);

            App.m_Proto[Account].IncomingUserInformation += new Protocols.Protocol.IncomingUserInformation2(IncomingUserInformation);

            App.m_Proto[Account].JoinChatError += new Protocols.Protocol.JoinChatError2(JoinChatError);

            App.m_Proto[Account].JoinedChat += new Protocols.Protocol.JoinedChat2(JoinedChat);

            App.m_Proto[Account].LoggedIn += new Protocols.Protocol.LoggedIn2(LoggedIn);

            App.m_Proto[Account].LoggedOut += new Protocols.Protocol.LoggedOut2(LoggedOut);

            App.m_Proto[Account].LoggingIn += new Protocols.Protocol.LoggingIn2(LoggingIn);

            App.m_Proto[Account].LoginError += new Protocols.Protocol.LoginError2(LoginError);
        }

        void LoginError(int Account, string Error)
        {
            Dispatcher.BeginInvoke(() =>
            {
                App.Accounts.Items[Account].SignedOn = false;

                MessageBox.Show(Error);
            });
        }

        void LoggingIn(int Account, double CurrentStatus)
        {
            Dispatcher.BeginInvoke(() =>
            {
                App.Accounts.Items[Account].SignedOn = true;

                App.setProgressIndication(this, true, true, "Connecting", CurrentStatus);
            });
        }

        void LoggedOut(int Account)
        {
            Dispatcher.BeginInvoke(() =>
            {
                App.Accounts.Items[Account].SignedOn = false;

                for (int i = 0; i < App.Contacts.Count; i++)
                {
                    if (App.Contacts[i].UserAccount == Account)
                        App.Contacts.RemoveAt(i);
                }
            });
        }

        void LoggedIn(int Account)
        {
            Dispatcher.BeginInvoke(() =>
            {
                App.Accounts.Items[Account].SignedOn = true;

                App.setProgressIndication(this, false, false, "", 100);
            });
        }

        void JoinedChat(int Account, string Chat, int Exchange, int Type)
        {
            Dispatcher.BeginInvoke(() =>
            {
                noChatsTextBlock.Visibility = Visibility.Collapsed;

                MsgGroup group1 = new MsgGroup("Chat Rooms");

                group1.Add(new Message(Account, Chat.ToLower().Replace(" ", ""), Chat.ToLower().Replace(" ", ""), Chat.ToLower().Replace(" ", ""), "You have successfully joined.", new Uri("Images/Protocols/AIM.png", UriKind.Relative), new Uri("Images/Chats/chat.png", UriKind.Relative), new Uri("Images/Buddylist/Status/available.png", UriKind.Relative)));

                App.Chats.Add(group1);

                App.Chats[0][App.Chats.Count - 1].Tag = (App.Chats[0].Count - 1).ToString();
            });
        }

        void JoinChatError(int Account, string Chat, string Error)
        {
            Dispatcher.BeginInvoke(() =>
            {
                MessageBox.Show(Error, "Error Joining: " + Chat, MessageBoxButton.OK);
            });
        }

        void IncomingUserInformation(int Account, string Screenname, string Profile, int Status)
        {
            Dispatcher.BeginInvoke(() =>
            {

            });
        }

        void IncomingUserIcon(int Account, string Screenname, System.Windows.Media.Imaging.BitmapImage Avatar)
        {
            Dispatcher.BeginInvoke(() =>
            {
                int RealBuddyID = 0, RealGroupID = 0;

                bool foundBuddy = false;

                for (int i = 0; i < App.Contacts.Count; i++)
                {
                    for (int x = 0; x < App.Contacts[i].Count; x++)
                    {
                        if (App.Contacts[i][x].RScreenname == Screenname && App.Contacts[i].UserAccount == Account)
                        {
                            RealGroupID = i;
                            RealBuddyID = x;
                            foundBuddy = true;
                            break;
                        }
                    }

                    if (foundBuddy == true)
                        break;
                }

                if (Avatar != null)
                    App.Contacts[RealGroupID][RealBuddyID].BuddyIcon = Avatar.UriSource;
            });
        }

        void IncomingICBM(int Account, string Screenname, string Message)
        {
            Dispatcher.BeginInvoke(() =>
            {

            });
        }

        void IncomingChatMessage(int Account, string Screenname, string Message)
        {
            Dispatcher.BeginInvoke(() =>
            {

            });
        }

        void IncomingChatInvite(int Account, string Screenname, string InviteMessage, string Chat, string Exchange, string Type, string Instance, string Details)
        {
            Dispatcher.BeginInvoke(() =>
            {
                if (MessageBox.Show(InviteMessage, Screenname + " has invited you to " + Chat, MessageBoxButton.OKCancel) == MessageBoxResult.OK)
                {
                    App.m_Proto[Account].JoinChat(Chat, Exchange, Type, Instance, Details);
                }
            });
        }

        void BuddyStatusUpdate(int Account, string BuddyName, int Status, string StatusMessage)
        {
            Dispatcher.BeginInvoke(() =>
            {
                int RealBuddyID = 0, RealGroupID = 0;

                bool foundBuddy = false;

                for (int i = 0; i < App.Contacts.Count; i++)
                {
                    for (int x = 0; x < App.Contacts[i].Count; x++)
                    {
                        if (App.Contacts[i][x].RScreenname == BuddyName && App.Contacts[i].UserAccount == Account)
                        {
                            RealGroupID = i;
                            RealBuddyID = x;
                            foundBuddy = true;
                            break;
                        }
                    }

                    if (foundBuddy == true)
                        break;
                }
                
                Uri status = new Uri("Images/Buddylist/Status/offline.png", UriKind.Relative);

                switch (Status)
                {
                    case 0:
                        status = new Uri("Images/Buddylist/Status/offline.png", UriKind.Relative);
                        App.Contacts[RealGroupID][RealBuddyID].BuddyStatus = "Offline";
                        break;
                    case 268566528:
                        status = new Uri("Images/Buddylist/Status/available.png", UriKind.Relative);
                        App.Contacts[RealGroupID][RealBuddyID].BuddyStatus = "Online";
                        break;
                    case 268566529:
                        status = new Uri("Images/Buddylist/Status/away.png", UriKind.Relative);
                        App.Contacts[RealGroupID][RealBuddyID].BuddyStatus = "Away";
                        break;               
                    default:
                        status = new Uri("Images/Buddylist/Status/invisible.png", UriKind.Relative);
                        App.Contacts[RealGroupID][RealBuddyID].BuddyStatus = "Invisible";
                        break;
                }

                App.Contacts[RealGroupID][RealBuddyID].UserStatus = status;

                if (StatusMessage != null && StatusMessage.Length > 0)
                    App.Contacts[RealGroupID ][RealBuddyID].BuddyStatus = StatusMessage;
            });
        }

        void BuddyItem(int Account, string BuddyName, int GroupID, int BuddyID)
        {
            Dispatcher.BeginInvoke(() =>
            {
                int RealID = 0;

                for (int i = 0; i < App.Contacts.Count; i++)
                {
                    if (App.Contacts[i].ID == GroupID && App.Contacts[i].UserAccount == Account)
                    {
                        RealID = i;
                        break;
                    }
                }

                App.Contacts[RealID].Add(new Buddy(BuddyName, BuddyName, BuddyName, "Offline", App.Accounts.Items[Account].pProtocol, new Uri("Images/Buddylist/Avatar.png", UriKind.Relative), new Uri("Images/Buddylist/Status/offline.png", UriKind.Relative)));
            });
        }

        void BuddyGroup(int Account, string GroupName, int GroupID)
        {
            Dispatcher.BeginInvoke(() =>
            {
                Group group = new Group(GroupName, GroupID, Account);

                App.Contacts.Add(group);

                noGroupsTextBlock.Visibility = Visibility.Collapsed;
            });
        }

        void BuddyChatUpdate(int Account, string Chat, int Exchange, int Type, string Username, bool EnteredRoom)
        {
            Dispatcher.BeginInvoke(() =>
            {

            });
        }

        void MainPage_BackKeyPress(object sender, System.ComponentModel.CancelEventArgs e)
        {
            if (App.confirmExit == true)
            {
                if (MessageBox.Show("Are you sure you would like to close Groovy IM?", "Close Groovy IM?", MessageBoxButton.OKCancel) == MessageBoxResult.Cancel)
                {
                    e.Cancel = true;
                    return;
                }
            }
        }

        void MainPage_Loaded(object sender, RoutedEventArgs e)
        {
            App.systemTrayBar(App.SystemTrayIsVisible);

            if (App.SystemTrayIsVisible)
                showADs.Margin = new Thickness(0, 615, 0, 0);
            else
                showADs.Margin = new Thickness(0, 647, 0, 0);

            SupportedOrientations = App.Orientation;
            
            buddyList.ItemsSource = App.Contacts;

            chatList.ItemsSource = App.Chats;
        }

        private void PhoneApplicationPage_OrientationChanged(object sender, OrientationChangedEventArgs e)
        {

        }

        private void addGroup(object sender, EventArgs e)
        {
            //NavigationService.Navigate(new Uri("/AddContactPage.xaml", UriKind.Relative));
        }

        private void help(object sender, EventArgs e)
        {
            NavigationService.Navigate(new Uri("/HelpPage.xaml", UriKind.Relative));
        }

        private void joinChat(object sender, EventArgs e)
        {
            NavigationService.Navigate(new Uri("/JoinChatPage.xaml", UriKind.Relative));
        }

        private void manageAccounts(object sender, EventArgs e)
        {
            NavigationService.Navigate(new Uri("/ManageAccounts.xaml?Window=0", UriKind.Relative));
        }

        private void searchContacts(object sender, EventArgs e)
        {

        }

        private void searchConversations(object sender, EventArgs e)
        {

        }

        private void sendIM(object sender, EventArgs e)
        {
            NavigationService.Navigate(new Uri("/SendIMPage.xaml", UriKind.Relative));
        }

        private void settings(object sender, EventArgs e)
        {
            NavigationService.Navigate(new Uri("/SettingsPage.xaml", UriKind.Relative));
        }

        private void Pivot_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            Dispatcher.BeginInvoke(new ThreadStart(updateAppBar)); 
        }

        private void updateAppBar()
        {
            updateButtonMnu(0, null, null, false, null);
            updateMenuMnu(0, null, false, null);
            updateButtonMnu(0, null, null, false, null);
            updateMenuMnu(0, null, false, null);
            updateButtonMnu(0, null, null, false, null);
            updateMenuMnu(0, null, false, null);
            updateButtonMnu(0, null, null, false, null);
            updateMenuMnu(0, null, false, null);

            switch (pivSwitch.SelectedIndex)
            {
                case 0:
                    updateButtonMnu(0, "/Images/App/AppBar/appbar.feature.account.rest.png", "accounts", true, new EventHandler(manageAccounts));
                    updateButtonMnu(1, "/Images/App/AppBar/appbar.feature.add.group.png", "add group", true, new EventHandler(addGroup));
                    updateButtonMnu(2, "/Images/App/AppBar/appbar.feature.search.rest.png", "search", true, new EventHandler(searchContacts));
                    updateButtonMnu(3, "/Images/App/AppBar/appbar.feature.settings.rest.png", "settings", true, new EventHandler(settings));
                    updateMenuMnu(0, "help", true, new EventHandler(help));
                    break;
                case 1:
                    updateButtonMnu(0, "/Images/App/AppBar/appbar.feature.send.im.png", "send im", true, new EventHandler(sendIM));
                    updateButtonMnu(1, "/Images/App/AppBar/appbar.feature.join.chat.png", "group chat", true, new EventHandler(joinChat));
                    updateButtonMnu(2, "/Images/App/AppBar/appbar.feature.search.rest.png", "search", true, new EventHandler(searchConversations));
                    updateButtonMnu(3, "/Images/App/AppBar/appbar.feature.settings.rest.png", "settings", true, new EventHandler(settings));
                    updateMenuMnu(0, "help", true, new EventHandler(help));
                    break;
                case 2:
                    updateButtonMnu(0, "/Images/App/AppBar/appbar.feature.settings.rest.png", "settings", true, new EventHandler(settings));
                    updateButtonMnu(1, "/Images/App/AppBar/appbar.questionmark.rest.png", "help", true, new EventHandler(help));
                    break;
            }
        }

        private void updateButtonMnu(int Index, string uriString, string Text, bool Visibile, EventHandler Handler)
        {
            ApplicationBarIconButton button = null;

            if (ApplicationBar.Buttons.Count > Index)
            {
                button = ApplicationBar.Buttons[Index] as ApplicationBarIconButton;
            }

            if (button != null)
            {
                {
                    ApplicationBar.Buttons.Remove(button);
                }
            }

            if (Visibile == true)
            {
                button = new ApplicationBarIconButton(new Uri(uriString, UriKind.Relative));
                button.Text = Text;
                button.Click += Handler;
                ApplicationBar.Buttons.Insert(Index, button);
            }
        }

        private void updateMenuMnu(int Index, string Text, bool Visibile, EventHandler Handler)
        {
            ApplicationBarMenuItem menu = null;

            if (ApplicationBar.MenuItems.Count > Index)
            {
                menu = ApplicationBar.MenuItems[Index] as ApplicationBarMenuItem;
            }

            if (menu != null)
            {
                {
                    ApplicationBar.MenuItems.Remove(menu);
                }
            }

            if (Visibile == true)
            {
                menu = new ApplicationBarMenuItem(Text);
                menu.Text = Text;
                menu.Click += Handler;
                ApplicationBar.MenuItems.Insert(Index, menu);
            }
        }

        private void ChatCollapse_Tap(object sender, System.Windows.Input.GestureEventArgs e)
        {
            TextBlock clickedTextBlock = sender as TextBlock;

            if (clickedTextBlock != null)
            {
                MsgGroup clickedGroup = clickedTextBlock.Tag as MsgGroup;

                if (clickedGroup != null)
                {
                    if (collapsedGroups2.ContainsKey(clickedGroup.Key))
                    {
                        collapsedGroups2.Remove(clickedGroup.Key);

                        foreach (var member in clickedGroup)
                        {
                            member.CollapseVisibility = Visibility.Visible;
                        }
                    }
                    else
                    {
                        collapsedGroups2.Add(clickedGroup.Key, clickedGroup);

                        foreach (var member in clickedGroup)
                        {
                            member.CollapseVisibility = Visibility.Collapsed;
                        }
                    }
                }
            }
        }

        private void GroupCollapse_Tap(object sender, System.Windows.Input.GestureEventArgs e)
        {
            TextBlock clickedTextBlock = sender as TextBlock;

            if (clickedTextBlock != null)
            {
                Group clickedGroup = clickedTextBlock.Tag as Group;

                if (clickedGroup != null)
                {
                    if (collapsedGroups.ContainsKey(clickedGroup.Key))
                    {
                        collapsedGroups.Remove(clickedGroup.Key);

                        foreach (var member in clickedGroup)
                        {
                            member.CollapseVisibility = Visibility.Visible;
                        }
                    }
                    else
                    {
                        collapsedGroups.Add(clickedGroup.Key, clickedGroup);

                        foreach (var member in clickedGroup)
                        {
                            member.CollapseVisibility = Visibility.Collapsed;
                        }
                    }
                }
            }
        }

        private void BuddylistItem_Tap(object sender, System.Windows.Input.GestureEventArgs e)
        {
            StackPanel stackPanel = sender as StackPanel;

            if (stackPanel != null)
            {
                Buddy clickedMember = (Buddy)stackPanel.Tag;

                NavigationService.Navigate(new Uri("/MessagePage.xaml?Screenname=" + clickedMember.Screenname, UriKind.Relative));
            }
        }

        private void TextBlock_Tap(object sender, System.Windows.Input.GestureEventArgs e)
        {
            string sTag;

            if ((sender as TextBlock) != null)
                sTag = (sender as TextBlock).Tag.ToString();
            else
                sTag = (sender as Image).Tag.ToString();

            NavigationService.Navigate(new Uri("/ChatPage.xaml?MsgID=" + sTag, UriKind.Relative));
        }
    }
}